package com.cxb.springboot.controller;

import com.cxb.springboot.config.ZkConfiguration;
import com.cxb.springboot.service.CuratorLockService;
import lombok.extern.slf4j.Slf4j;
import org.apache.curator.framework.recipes.locks.InterProcessMutex;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.ResponseBody;

/**
 * @Classname MicroController
 * @Description TODO
 * @Date 2023/3/28 22:03
 * @Created by Administrator
 */
@Controller
@RequestMapping("/zk")
@Slf4j
public class MicroController {

    private final static String PATH = "/rootLock";

    private final static String ID_PATH = "/root/rootId";

    @Autowired
    ZkConfiguration zkConfiguration;

    @Autowired
    private CuratorLockService curatorLockService;

    /**
     * 这里我用的是最常用的可重入排他锁，也是公平锁（InterProcessMutex）
     * InterProcessMutex：分布式可重入排它锁
     * InterProcessSemaphoreMutex：分布式排它锁
     * InterProcessReadWriteLock：分布式读写锁
     * InterProcessMultiLock：将多个锁作为单个实体管理的容器
     * @return
     * @throws Exception
     */
    @GetMapping("/lock")
    @ResponseBody
    public String getLock1() throws Exception {
        InterProcessMutex lock = new InterProcessMutex(zkConfiguration.curatorFrameworkClient(), PATH);
        for (int i = 0; i < 30; i++) {
            Thread thread = new Thread(new Runnable() {
                @Override
                public void run() {
                    try {
                        log.info(Thread.currentThread().getName() + "尝试获取锁....");
                        lock.acquire();
                        log.info(Thread.currentThread().getName() + "获取锁成功....");
                        log.info(Thread.currentThread().getName() + "开始执行业务逻辑....");
                        Thread.sleep(10000);
                        lock.release();
                        log.info(Thread.currentThread().getName() + "释放锁成功....");
                    } catch (Exception e) {
                        e.printStackTrace();
                    }
                }
            });
            thread.start();
        }
        return "execute success";
    }

    @GetMapping("/id")
    @ResponseBody
    public String createId(String data) throws Exception {
        return curatorLockService.getDistributedId(ID_PATH, data);
    }

}
